home *** CD-ROM | disk | FTP | other *** search
/ .net (French) 1996 December / .net Magazine (FR) - Issue 02 - Dec 1996.iso / Utilpers / SUPERQUE / DATA.2 / FILTERS / PSINIT / GS_RES.PS < prev    next >
Text File  |  1995-11-15  |  14KB  |  515 lines

  1. %    Copyright (C) 1994 Aladdin Enterprises.  All rights reserved.
  2. %    Licensed to Zenographics Inc. (Irvine, California) by Artifex Software Inc.
  3. %    under the OEM Agreement of December 21st, 1993.
  4.  
  5.  
  6. % Initialization file for Level 2 resource machinery.
  7. % When this is run, systemdict is still writable,
  8. % but everything defined here goes into level2dict.
  9.  
  10. level2dict begin
  11.  
  12. (BEGIN RESOURCES) VMDEBUG
  13.  
  14. % We keep track of (global) instances with another entry in the resource
  15. % dictionary, an Instances dictionary.  For categories with implicit
  16. % instances, the values in Instances are the same as the keys;
  17. % for other categories, the values are [instance status size].
  18.  
  19. % Note that the dictionary that defines a resource category is stored
  20. % in global memory.  The PostScript manual says that each category must
  21. % manage global and local instances separately.  However, objects in
  22. % global memory other than systemdict can't reference objects in local memory.
  23. % This means that the resource category dictionary, which would otherwise be
  24. % the obvious place to keep track of the instances, can't be used to keep
  25. % track of local instances.  Instead, we define a dictionary in local VM
  26. % called localinstancedict, in which the key is the category name and
  27. % the value is the analogue of Instances for local instances.
  28.  
  29. % We don't currently implement automatic resource unloading.
  30. % When we do, it should be hooked to the garbage collector.
  31.  
  32. currentglobal false setglobal systemdict begin
  33.   /localinstancedict 5 dict def
  34. end true setglobal
  35. /.emptydict 0 dict readonly def
  36. setglobal
  37.  
  38. % Resource category dictionaries have the following keys (those marked with
  39. % * are optional):
  40. %    Standard, defined in the Red Book:
  41. %        Category (name)
  42. %        *InstanceType (name)
  43. %        DefineResource
  44. %        UndefineResource
  45. %        FindResource
  46. %        ResourceStatus
  47. %        ResourceForAll
  48. %        *ResourceFileName
  49. %    Additional, specific to our implementation:
  50. %        Instances (dictionary)
  51. %        .LocalInstances
  52. %            - .LocalInstances <dict>
  53. %        .GetInstance
  54. %            <key> .GetInstance <instance> -true-
  55. %            <key> .GetInstance -false-
  56. %        .CheckResource
  57. %            <value> .CheckResource <ok>
  58. %        .DoLoadResource
  59. %            <key> .DoLoadResource - (may give an error)
  60. %        .LoadResource
  61. %            <key> .LoadResource - (may give an error)
  62. %        .ResourceFile
  63. %            <key> .ResourceFile <file> -true-
  64. %            <key> .ResourceFile <key> -false-
  65. % All the above procedures expect that the top dictionary on the d-stack
  66. % is the resource dictionary.
  67.  
  68. % Define enough of the Category category so we can define other categories.
  69. % The dictionary we're about to create will become the Category
  70. % category definition dictionary.
  71.  
  72. 12 dict begin
  73.  
  74.         % Standard entries
  75.  
  76. /Category /Category def
  77. /InstanceType /dicttype def
  78.  
  79. /DefineResource
  80.     { dup .CheckResource
  81.        { dup /Category 3 index cvlit .growput readonly
  82.          dup [ exch 0 -1 ] exch
  83.          Instances 4 2 roll put
  84.        }
  85.        { /typecheck signalerror
  86.        }
  87.       ifelse
  88.     } bind def
  89. /FindResource        % (redefined below)
  90.     { Instances exch get 0 get
  91.     } bind def
  92.  
  93.         % Additional entries
  94.  
  95. /Instances 25 dict def
  96. Instances /Category [currentdict 0 -1] put
  97.  
  98. /.LocalInstances 0 dict def
  99. /.GetInstance
  100.     { Instances exch .knownget
  101.     } bind def
  102. /.CheckResource
  103.     { dup gcheck currentglobal and
  104.        { /DefineResource /FindResource /ResourceForAll /ResourceStatus
  105.          /UndefineResource }
  106.        { 2 index exch known and }
  107.       forall exch pop
  108.     } bind def
  109.  
  110. Instances end begin    % for the base case of findresource
  111.  
  112. (END CATEGORY) VMDEBUG
  113.  
  114. % Define the resource operators.  I don't see how we can possibly restore
  115. % the stacks after an error, since the procedure may have popped and
  116. % pushed elements arbitrarily....
  117.  
  118. mark
  119. /defineresource
  120.     { /Category findresource dup begin
  121.       /InstanceType known
  122.        { dup type InstanceType ne
  123.           { dup type /packedarraytype eq InstanceType /arraytype eq and
  124.         not { /typecheck signalerror } if
  125.           } if
  126.        } if
  127.       /DefineResource load stopped end { stop } if
  128.     }
  129. /findresource
  130.     { dup /Category eq
  131.        { pop //Category 0 get } { /Category findresource } ifelse
  132.       begin
  133.       /FindResource load stopped end { stop } if
  134.     }
  135. /resourceforall
  136.     { /Category findresource begin
  137.       /ResourceForAll load stopped end { stop } if
  138.     }
  139. /resourcestatus
  140.     { /Category findresource begin
  141.       /ResourceStatus load stopped end { stop } if
  142.     }
  143. /undefineresource
  144.     { /Category findresource begin
  145.       /UndefineResource load stopped end { stop } if
  146.     }
  147. end        % Instances of Category
  148. counttomark 2 idiv { bind odef } repeat pop
  149.  
  150. % Define the Generic category.
  151.  
  152. /Generic mark
  153.  
  154.         % Standard entries
  155.  
  156. % We're still running in Level 1 mode, so dictionaries won't expand.
  157. % Leave room for the /Category entry.
  158. /Category null
  159.  
  160. /DefineResource
  161.     { dup .CheckResource
  162.        { dup [ exch 0 -1 ] exch
  163.          currentglobal
  164.           { false setglobal 2 index UndefineResource    % remove local def if any
  165.         true setglobal
  166.         Instances dup //.emptydict eq
  167.          { pop 3 dict /Instances 1 index def
  168.          }
  169.         if
  170.           }
  171.           { .LocalInstances dup //.emptydict eq
  172.              { pop 3 dict localinstancedict Category 2 index put
  173.          }
  174.         if
  175.           }
  176.          ifelse
  177.          4 2 roll .growput
  178.        }
  179.        { /typecheck signalerror
  180.        }
  181.       ifelse
  182.     } bind
  183. /UndefineResource
  184.     {  { dup 2 index .knownget
  185.           { dup 1 get 1 ge
  186.          { dup 0 null put 1 2 put pop pop }
  187.          { pop exch undef }
  188.         ifelse
  189.           }
  190.           { pop pop
  191.           }
  192.          ifelse
  193.        }
  194.       currentglobal
  195.        { 2 copy Instances exch exec
  196.        }
  197.       if .LocalInstances exch exec
  198.     } bind
  199. /FindResource
  200.     { dup ResourceStatus
  201.        { pop 1 gt            % not in VM
  202.           { .DoLoadResource
  203.           }
  204.          if
  205.          .GetInstance pop        % can't fail
  206.          0 get
  207.        }
  208.        { /undefinedresource signalerror
  209.        }
  210.       ifelse
  211.     } bind
  212. /ResourceStatus
  213.     { dup .GetInstance
  214.        { exch pop dup 1 get exch 2 get true }
  215.        { .ResourceFile
  216.           { closefile 2 -1 true }
  217.           { pop false }
  218.          ifelse
  219.        }
  220.       ifelse
  221.     } bind
  222. /ResourceForAll
  223.     { % **************** Doesn't present instance groups in
  224.       % **************** the correct order yet.
  225.       % We construct a new procedure so we don't have to use
  226.       % static resources to hold the iteration state.
  227.       3 packedarray        % template, proc, scratch
  228.       { exch pop    % stack contains: key, {template, proc, scratch}
  229.         2 copy 0 get .stringmatch
  230.          { 1 index type dup /stringtype eq exch /nametype eq or
  231.         { 2 copy 2 get cvs
  232.           exch 1 get 3 -1 roll pop
  233.         }
  234.         { 1 get
  235.         }
  236.            ifelse exec
  237.          }
  238.          { pop pop
  239.          }
  240.         ifelse
  241.       } /exec cvx 3 packedarray cvx
  242.       % We must pop the resource dictionary off the dict stack
  243.       % when doing the actual iteration, and restore it afterwards.
  244.       currentglobal .LocalInstances length 0 eq or not
  245.        {        % We must do local instances, and do them first.
  246.          /forall cvx 1 index currentdict 3 packedarray cvx
  247.          .LocalInstances 3 1 roll end exec begin
  248.        }
  249.       if
  250.       Instances exch
  251.       /forall cvx currentdict 2 packedarray cvx
  252.       end exec begin
  253.     } bind
  254.  
  255.         % Additional entries
  256.  
  257. % Unfortunately, we can't create the real Instances dictionary now,
  258. % because if someone copies the Generic category (which pp. 95-96 of the
  259. % 2nd Edition Red Book says is legitimate), they'll wind up sharing
  260. % the Instances.  Instead, we have to create Instances on demand,
  261. % just like the entry in localinstancedict.
  262. % We also have to prevent anyone from creating instances of Generic itself.
  263. /Instances //.emptydict
  264.  
  265. /.LocalInstances
  266.     { localinstancedict Category .knownget not { //.emptydict } if
  267.     } bind
  268. /.GetInstance
  269.     { currentglobal
  270.        { Instances exch .knownget }
  271.        { .LocalInstances 1 index .knownget
  272.           { exch pop true }
  273.           { Instances exch .knownget }
  274.          ifelse
  275.        }
  276.       ifelse
  277.     } bind
  278. /.CheckResource
  279.     { pop true
  280.     } bind
  281. /.DoLoadResource
  282.     { dup vmstatus pop exch pop exch
  283.       .LoadResource
  284.       vmstatus pop exch pop exch sub
  285.       1 index .GetInstance not
  286.        { pop /undefinedresource signalerror }    % didn't load
  287.       if
  288.       dup 1 1 put
  289.       2 3 -1 roll put
  290.     } bind
  291. /.LoadResource
  292.     { dup .ResourceFile
  293.        { exch pop currentglobal
  294.           { run }
  295.           { true setglobal { run } stopped false setglobal { stop } if }
  296.          ifelse
  297.        }
  298.        { /undefinedresource signalerror
  299.        }
  300.      ifelse
  301.     } bind
  302. /.ResourceFile
  303.     { currentdict /ResourceFileName known
  304.        { mark 1 index 100 string { ResourceFileName }
  305.          stopped
  306.           { cleartomark false }
  307.           { exch pop findlibfile
  308.          { exch pop exch pop true }
  309.          { false }
  310.         ifelse
  311.           }
  312.          ifelse
  313.        }
  314.        { false }
  315.       ifelse
  316.     } bind
  317.  
  318. .dicttomark
  319. /Category defineresource pop
  320.  
  321. % Fill in the rest of the Category category.
  322. /Category /Category findresource dup
  323. /Generic /Category findresource begin
  324.  { /FindResource /ResourceForAll /ResourceStatus /UndefineResource /.ResourceFile }
  325.  { dup load put dup } forall
  326. pop readonly pop end
  327.  
  328. (END GENERIC) VMDEBUG
  329.  
  330. % Define the fixed categories.
  331.  
  332. mark
  333.     % Things other than types
  334.  /ColorSpaceFamily
  335.    mark colorspacedict { pop } forall .packtomark
  336.  /Emulator
  337.    mark EMULATORS { cvn } forall .packtomark
  338.  /Filter
  339.    mark filterdict { pop } forall .packtomark
  340.  /IODevice
  341.     % Loop until the .getiodevice gets a rangecheck.
  342.    errordict /rangecheck 2 copy get
  343.    errordict /rangecheck { pop stop } put    % pop the command
  344.    mark 0 { {dup .getiodevice exch 1 add} loop} stopped pop pop pop .packtomark
  345.    4 1 roll put
  346.    .clearerror
  347.     % Types
  348.  /setcolorrendering where
  349.   { pop /ColorRenderingType
  350.      {1}
  351.   } if
  352.  /.buildfont0 where
  353.   { pop /FMapType
  354.      {2 3 4 5 6 7 8}
  355.   } if
  356.  /FontType
  357.    [/.buildfont0 where {pop 0} if
  358.     /.buildfont1 where {pop 1} if
  359.     3]
  360.  /FormType
  361.    {1}
  362.  /HalftoneType
  363.    {1 2 3 4 5}
  364.  /ImageType
  365.    {1}
  366.  /PatternType
  367.    {1}            % should check for Pattern color space
  368. counttomark 2 idiv
  369.  { mark
  370.  
  371.         % Standard entries
  372.  
  373.    /DefineResource
  374.     { /invalidaccess signalerror } bind
  375.    /UndefineResource
  376.     { /invalidaccess signalerror } bind
  377.    /FindResource
  378.     { Instances exch get } bind
  379.    /ResourceStatus
  380.     { Instances exch known { 0 0 true } { false } ifelse } bind
  381.    /ResourceForAll
  382.     /Generic /Category findresource /ResourceForAll get
  383.  
  384.         % Additional entries
  385.  
  386.    counttomark 2 add -1 roll
  387.    dup length dict dup begin exch { dup def } forall end readonly
  388.    /Instances exch
  389.    /.LocalInstances    % used by ResourceForAll
  390.     0 dict def
  391.  
  392.    .dicttomark /Category defineresource pop
  393.  } repeat pop
  394.  
  395. (END FIXED) VMDEBUG
  396.  
  397. % Define the other built-in categories.
  398.  
  399. /.definecategory    % <name> -mark- <key1> ... <valuen> .definecategory -
  400.  { counttomark 2 idiv 2 add        % Instances, Category
  401.    /Generic /Category findresource dup maxlength 3 -1 roll add dict copy begin
  402.    counttomark 2 idiv { def } repeat pop    % pop the mark
  403.    currentdict end /Category defineresource pop
  404.  } bind def
  405.  
  406. /ColorRendering mark /InstanceType /dicttype .definecategory
  407. /ColorSpace mark /InstanceType /arraytype .definecategory
  408. /Form mark /InstanceType /dicttype .definecategory
  409. /Halftone mark /InstanceType /dicttype .definecategory
  410. /Pattern mark /InstanceType /dicttype .definecategory
  411. /ProcSet mark /InstanceType /dicttype .definecategory
  412.  
  413. (END MISC) VMDEBUG
  414.  
  415. % Define the Encoding category.
  416.  
  417. /Encoding mark
  418.  
  419. /InstanceType /arraytype
  420.  
  421. % Handle lazily loaded encodings that aren't loaded yet.
  422.  
  423. /Instances mark
  424.   .encodingdict
  425.    { length 256 eq { pop } { [null 2 -1] } ifelse
  426.    } forall
  427. .dicttomark
  428.  
  429. /.ResourceFileDict mark
  430.   .encodingdict
  431.    { dup length 256 eq { pop pop } { 0 get } ifelse
  432.    } forall
  433. .dicttomark
  434.  
  435. /ResourceFileName
  436.  { exch dup .ResourceFileDict exch .knownget
  437.     { exch pop exch copy }
  438.     { exch pop /undefinedresource signalerror }
  439.    ifelse
  440.  } bind
  441.  
  442. .definecategory            % Encoding
  443.  
  444. /.findencoding { /Encoding findresource } bind def
  445. /findencoding /.findencoding load odef
  446. /.defineencoding
  447.  { 2 copy /Encoding defineresource pop
  448.    //.encodingdict 3 1 roll put
  449.  } bind def
  450.  
  451. (END ENCODING) VMDEBUG
  452.  
  453. % Define the Font category.
  454.  
  455. /Font mark
  456.  
  457. /InstanceType /dicttype
  458.  
  459. /DefineResource
  460.     { 2 copy //definefont exch pop
  461.       /Generic /Category findresource /DefineResource get exec
  462.     } bind
  463. /UndefineResource
  464.     { dup //undefinefont
  465.       /Generic /Category findresource /UndefineResource get exec
  466.     } bind
  467. /FindResource
  468.     { dup ResourceStatus
  469.        { pop 1 gt { .DoLoadResource } if }
  470.        { .DoLoadResource }
  471.       ifelse
  472.       .GetInstance pop 0 get
  473.       __fixupstubfont
  474.     } bind
  475.  
  476. /.LoadResource
  477.     { //findfont exec pop
  478.     } bind
  479.  
  480. /Instances FontDirectory length 2 mul dict
  481.  
  482. .definecategory            % Font
  483.  
  484. % Make entries for fonts already loaded.
  485. /Font /Category findresource begin
  486. FontDirectory
  487.  { dup .gcheck { Instances } { .LocalInstances } ifelse
  488.    3 1 roll [exch 0 -1] .growput
  489.  }
  490. forall end
  491.  
  492. % Redefine font "operators".
  493. /.definefontmap
  494.  { /Font /Category findresource /Instances get
  495.    dup 3 index known
  496.     { pop }
  497.     { 2 index [null 2 -1] .growput }
  498.    ifelse
  499.    //.definefontmap exec
  500.  } bind def
  501. Fontmap { .definefontmap } forall
  502.  
  503. /definefont
  504.     { /Font defineresource } bind odef
  505. /undefinefont
  506.     { /Font undefineresource } bind odef
  507. /findfont
  508.     { /Font findresource } bind def    % Must be a procedure, not an operator
  509.  
  510. % Remove initialization utilities.
  511. currentdict /.definecategory undef
  512. currentdict /.emptydict undef
  513.  
  514. end                % level2dict
  515.